import 'dart:math' as math;

import 'package:boss/ui/page/reportForm/order/provider/order_provider.dart';
import 'package:boss/ui/page/reportForm/order/widget/order_header_bar.dart';
import 'package:boss/ui/page/reportForm/order/widget/order_status_bar.dart';
import 'package:boss/ui/widget/calendar_bar.dart';
import 'package:hi_common/hi_common.dart';
import 'package:flutter/material.dart';
import 'package:flutter/rendering.dart';
import 'package:provider/provider.dart';

class OrderFilterPanel extends StatefulWidget {
  @override
  _OrderFilterPanelState createState() => _OrderFilterPanelState();
}

class _OrderFilterPanelState extends State<OrderFilterPanel> with TickerProviderStateMixin {
  FloatingHeaderSnapConfiguration _snapConfiguration;

  @override
  void initState() {
    super.initState();

    _snapConfiguration = FloatingHeaderSnapConfiguration(
      curve: Curves.easeOut,
      duration: const Duration(milliseconds: 200),
      vsync: this,
    );
  }

  @override
  void dispose() {
    _snapConfiguration = null;
    super.dispose();
  }

  @override
  Widget build(BuildContext context) {
    return SliverPersistentHeader(
      pinned: false,
      floating: true,
      delegate: _CustomOrderFilterPanelDelegate(
        snapConfiguration: _snapConfiguration,
        topPadding: MediaQuery.of(context).padding.top,
      ),
    );
  }
}

class _CustomOrderFilterPanelDelegate extends SliverPersistentHeaderDelegate {
  double topPadding;

  _CustomOrderFilterPanelDelegate({
    @required this.snapConfiguration,
    @required this.topPadding,
  });

  @override
  Widget build(BuildContext context, double shrinkOffset, bool overlapsContent) {
    final Widget appBar = FlexibleSpaceBar.createSettings(
      minExtent: minExtent,
      maxExtent: maxExtent,
      currentExtent: math.max(minExtent, maxExtent - shrinkOffset),
      toolbarOpacity: 1,
      child: Semantics(
        child: Container(
          color: Colors.white,
          child: Column(
            crossAxisAlignment: CrossAxisAlignment.start,
            children: <Widget>[
              Container(
                child: Consumer<OrderProvider>(
                  builder: (context, orderProvider, _) {
                    return CalendarBar(
                      startDateTime: orderProvider.startTime,
                      endDateTime: orderProvider.endTime,
                      onDateTimeChanged: orderProvider.setStartTime,
                      type: CalendarType.ymdhm,
                    );
                  },
                ),
                margin: EdgeInsets.only(top: 26.w, bottom: 20.w),
                padding: EdgeInsets.symmetric(horizontal: 30.w),
              ),
              Consumer<OrderProvider>(
                builder: (context, orderProvider, _) {
                  return OrderHeaderBar(
                    title: '店铺订单',
                    orderCount: orderProvider.orderHeader?.num ?? 0,
                    price: orderProvider.orderHeader?.totalFee ?? 0,
                  );
                },
              ),
              OrderStatusBar(),
            ],
          ),
        ),
        header: true,
      ),
    );

    return _OrderFilterPanelFloating(
      child: appBar,
    );
  }

  double get height => ScreenUtil.instance.setHeight(110.0 + 64 + 40) + 164.w;

  @override
  double get maxExtent => height;

  @override
  double get minExtent => height;

  @override
  bool shouldRebuild(SliverPersistentHeaderDelegate oldDelegate) {
    return true;
  }

  @override
  final FloatingHeaderSnapConfiguration snapConfiguration;
}

class _OrderFilterPanelFloating extends StatefulWidget {
  const _OrderFilterPanelFloating({Key key, this.child}) : super(key: key);

  final Widget child;

  @override
  _OrderFilterPanelFloatingState createState() => _OrderFilterPanelFloatingState();
}

class _OrderFilterPanelFloatingState extends State<_OrderFilterPanelFloating> {
  ScrollPosition _position;

  @override
  void didChangeDependencies() {
    super.didChangeDependencies();
    if (_position != null) _position.isScrollingNotifier.removeListener(_isScrollingListener);
    _position = Scrollable.of(context)?.position;
    if (_position != null) _position.isScrollingNotifier.addListener(_isScrollingListener);
  }

  @override
  void dispose() {
    if (_position != null) _position.isScrollingNotifier.removeListener(_isScrollingListener);
    super.dispose();
  }

  RenderSliverFloatingPersistentHeader _headerRenderer() {
    return context.ancestorRenderObjectOfType(const TypeMatcher<RenderSliverFloatingPersistentHeader>());
  }

  void _isScrollingListener() {
    if (_position == null) return;

    // When a scroll stops, then maybe snap the appbar into view.
    // Similarly, when a scroll starts, then maybe stop the snap animation.
    final RenderSliverFloatingPersistentHeader header = _headerRenderer();
    if (_position.isScrollingNotifier.value)
      header?.maybeStopSnapAnimation(_position.userScrollDirection);
    else
      header?.maybeStartSnapAnimation(_position.userScrollDirection);
  }

  @override
  Widget build(BuildContext context) => widget.child;
}
